package com.polaris.live.utils.route

import android.app.Activity
import android.content.Intent
import android.graphics.Color
import android.text.TextPaint
import android.text.style.ClickableSpan
import android.view.View
import android.widget.TextView
import androidx.appcompat.app.AppCompatActivity
import androidx.lifecycle.LifecycleOwner
import com.blankj.utilcode.util.ActivityUtils
import com.blankj.utilcode.util.ColorUtils
import com.blankj.utilcode.util.EncodeUtils
import com.blankj.utilcode.util.SpanUtils
import com.polaris.live.R
import com.polaris.live.common.R.id
import com.polaris.live.common.cacha.DisplayUtil
import com.polaris.live.common.cacha.UserManager
import com.polaris.live.common.constant.AppConst
import com.polaris.live.common.constant.CommonConst
import com.polaris.live.common.constant.ServerConfig
import com.polaris.live.common.mvvm.activity.BaseVmActivity
import com.polaris.live.common.network.request
import com.polaris.live.common.util.JsonUtils
import com.polaris.live.common.util.ToastGravity
import com.polaris.live.common.util.ViewUtils
import com.polaris.live.constant.LiveConst
import com.polaris.live.constant.UserConst
import com.polaris.live.dialog.GlobalDialogManager
import com.polaris.live.im.manager.RouterControlManager
import com.polaris.live.im.sfs.bean.chat.ext.RouterHighlight
import com.polaris.live.manager.LiveStateManager
import com.polaris.live.net.homeService
import com.polaris.live.popup.GlobalPopupManager
import com.polaris.live.resp.event.MainRouterEvent
import com.polaris.live.resp.event.StartPartyRouterEvent
import com.polaris.live.resp.event.WebSpectatorEvent
import com.polaris.live.resp.go_resp.MatchStartBean
import com.polaris.live.ui.live.activity.LiveSpectatorActivity
import com.polaris.live.ui.luckybag.fragment.dialog.LuckyBagMessageDialogFragment
import com.polaris.live.ui.main.activity.MainActivity
import com.polaris.live.ui.party.PartyUserStateUtil
import com.polaris.live.ui.party.activity.PartySpectatorActivity
import com.polaris.live.ui.party.activity.game.PartyGameSpectatorActivity
import com.polaris.live.ui.web.WebActivity
import com.polaris.live.utils.CommonUtils
import com.polaris.live.utils.LiveUtils
import com.polaris.live.utils.StartLiveProxy
import com.polaris.live.utils.XActivityUtils
import com.polaris.live.utils.fragment.FragmentUtils
import com.polaris.live.utils.fragment.showNewDialogFragment
import org.apache.commons.lang.StringEscapeUtils
import org.greenrobot.eventbus.EventBus

/**
 * RouterUtils
 *
 * @author Created by lucas on 2023/10/24 09:48
 */
object RouterUtils {

    object Type {

        const val KEY_HTTP = "http"
        const val KEY_NATIVE = "native://"
        const val KEY_ACTION = "native://action="

    }

    //如果是游戏房 派对房 直播间观众页  点击路由后直接弹掉顶部的页面
    val paths = setOf(
        RoutePath.LIVE_SPECTATOR_ACTIVITY,
        RoutePath.PARTY_GAME_SPECTATOR_ACTIVITY,
        RoutePath.PARTY_SPECTATOR_ACTIVITY
    )

    /**
     * 处理文字
     */
    fun handleText(
        view: TextView,
        content: String,
        highlights: List<RouterHighlight>,
    ) {
        if (highlights.isEmpty()) {
            view.text = content
            return
        }

        val sortHighlights = highlights.sortedBy { it.s }
        view.text = SpanUtils.with(view)
            .apply {
                var lastEndIndex = 0

                sortHighlights.forEachIndexed { _, it ->
                    if (lastEndIndex != it.s) {
                        append(content.substring(lastEndIndex, it.s))
                    }

                    append(content.substring(it.s, it.e))
                    setForegroundColor(resolveColor(it.c))

                    lastEndIndex = it.e
                }

                if (lastEndIndex != content.length) {
                    append(content.substring(lastEndIndex))
                }
            }
            .create()
    }

    /**
     * 处理路由文字
     */
    fun handleRouterText(
        view: TextView,
        content: String,
        highlights: List<RouterHighlight>,
        routers: Map<String, String>,
    ) {
        if (highlights.isEmpty()) {
            view.text = content
            return
        }

        val sortHighlights = highlights.sortedBy { it.s }

        view.text = SpanClickUtils.with(view)
            .apply {
                var lastEndIndex = 0

                sortHighlights.forEachIndexed { index, it ->
                    if (lastEndIndex != it.s) {
                        append(content.substring(lastEndIndex, it.s))
                    }

                    append(content.substring(it.s, it.e))
                    val router = routers["highlight$index"]
                    if (router != null) {
                        val color = resolveColor(it.c)
                        setClickSpan(object : ClickableSpan() {
                            override fun updateDrawState(paint: TextPaint) {
                                paint.color = color
                                paint.isUnderlineText = true
                                paint.bgColor = Color.TRANSPARENT
                            }

                            override fun onClick(widget: View) {
                                routerGoto(router)
                            }
                        })
                    } else {
                        setForegroundColor(resolveColor(it.c))
                    }

                    lastEndIndex = it.e
                }

                if (lastEndIndex != content.length) {
                    append(content.substring(lastEndIndex))
                }
            }
            .create()
    }

    private fun resolveColor(color: String?): Int {
        return if (color == null) {
            ColorUtils.getColor(R.color.fe1849)
        } else {
            try {
                ColorUtils.string2Int(color)
            } catch (t: Throwable) {
                ColorUtils.getColor(R.color.fe1849)
            }
        }
    }

    /**
     * 路由跳转
     */
    fun routerGoto(router: String) {
        if (router.isEmpty()) {
            return
        }
        val url = router.trim()
        if (url.startsWith(Type.KEY_HTTP)) {
            routerWeb(url)
        } else if (url.startsWith(Type.KEY_NATIVE)) {
            if (url.startsWith(Type.KEY_ACTION)) {
                routerAction(url.substring(Type.KEY_ACTION.length))
            } else {
                routerRouter(url.substring(Type.KEY_NATIVE.length))
            }
        } else {
            showUnsupported(router)
        }
    }

    /**
     * 处理到子路由
     */
    fun routerGotoChild(activity: Activity, view: View? = null) {
        val hasGoto = if (view != null) {
            val tag = view.getTag(id.view_first)
            if (tag is Boolean) {
                tag
            } else {
                true
            }
        } else {
            true
        }

        if (!hasGoto) {
            return
        }

        val router = activity.intent.getStringExtra("router")
        router?.also {
            routerGoto(EncodeUtils.urlDecode(it))
        }

        view?.setTag(id.view_first, true)
    }

    private fun routerRouter(url: String) {
        val routerMap = parseRouter(url.substringBefore("?"))
        val androidUrl = routerMap["androidUrl"]
        if (androidUrl.isNullOrEmpty()) {
            showUnsupported(url)
            return
        }

        val params = parseRouter(url.substringAfter("?"))
        Router.builder(androidUrl)
            .apply {
                params.forEach { (k, v) ->
                    fillParam(k, v)
                }
            }
            .navigation()
    }

    /**
     * 获取anchorId
     * native://className=live&androidUrl=/live/LiveSpectatorActivity?anchorId=3574
     */
    fun getAnchorId(router: String?): Long? {
        if (router.isNullOrEmpty()) {
            return null
        }
        try {
            if (router.startsWith(Type.KEY_NATIVE) && !router.startsWith(Type.KEY_ACTION)) {
                val params = router.substringAfter("?")
                    .split("&")
                    .associate { param ->
                        val (key, value) = param.split("=")
                        key to value
                    }

                return params["anchorId"]?.toLongOrNull()
            }
        } catch (e: Exception) {
            // 异常捕获，返回 null
        }
        return null
    }

    private fun Router.fillParam(key: String, value: Any): Router {
        when (value) {
            is Boolean -> withBoolean(key, value)
            is Byte -> withByte(key, value)
            is Short -> withShort(key, value)
            is Int -> withInt(key, value)
            is Long -> withLong(key, value)
            is Float -> withFloat(key, value)
            is Double -> withDouble(key, value)
            is Char -> withChar(key, value)
            is String -> withString(key, value)
        }

        return this
    }

    fun routerGetPath(url: String): String {
        if (url.startsWith(Type.KEY_HTTP)) {
            return url
        } else if (url.startsWith(Type.KEY_NATIVE)) {
            if (url.startsWith(Type.KEY_ACTION)) {
                val routerUrl = url.substring(Type.KEY_ACTION.length)
                return routerUrl.substringBefore("?")
            } else {
                val routerUrl = url.substring(Type.KEY_NATIVE.length)
                val routerMap = parseRouter(routerUrl.substringBefore("?"))
                val androidUrl = routerMap["androidUrl"]
                if (androidUrl != null) {
                    return androidUrl
                }
            }
        }
        return ""
    }

    fun parseRouter(urlParams: String): Map<String, String> {
        if (urlParams.isEmpty()) {
            return emptyMap()
        }

        val params = StringEscapeUtils.unescapeHtml(urlParams)

        val split = params.split("&".toRegex())
        return buildMap {
            for (s in split) {
                if (s.startsWith("router=")) {
                    val map = s.split("=", limit = 2)
                    if (map.size == 2) {
                        this[map[0]] = map[1]
                    }
                } else {
                    val keyValue = s.split("=".toRegex())
                    if (keyValue.size == 2) {
                        this[keyValue[0]] = keyValue[1]
                    }
                }
            }
        }
    }

    /**
     * 跳转到网页
     */
    fun routerWeb(url: String, map: Map<String, String>? = null) {
        val topActivity = ViewUtils.getAliveTopActivity() ?: return
        val intent = Intent(topActivity, WebActivity::class.java)
        intent.putExtra("url", url)
        if (map != null) {
            intent.putExtra("parameter", JsonUtils.toJson(map))
        }
        topActivity.startActivity(intent)
    }

    /**
     * 客服转跳
     */
    fun routerCustomerService(url: String) {
        val topActivity = ViewUtils.getAliveTopActivity() ?: return
        Router.builder(RoutePath.WEB_ACTIVITY)
            .withString("url", url)
            .withInt("customer", AppConst.YES)
            .navigation(topActivity)
    }

    private fun routerAction(url: String) {
        when (url.substringBefore("?")) {
            "feedback" -> {
                Router.builder(RoutePath.FEEDBACK_AND_SUGGESTION).navigation()
            }

            "match" -> {
                val context = ViewUtils.getAliveTopActivity()
                if (context is BaseVmActivity<*>) {
                    GlobalPopupManager.showCompletePopup(context) {
                        //如果是男生点击 进入匹配
                        if (CommonUtils.isMan(UserManager.getUser().sex)) {
                            context.mViewModel.request(
                                {
                                    homeService.matchStart(
                                        MatchStartBean(
                                            CommonConst.MatchStart.MANUAL,
                                            UserConst.From.SINGLE
                                        )
                                    )
                                },
                                {
                                    Router.builder(RoutePath.LIVE_MATCH_ACTIVIYT)
                                        .withInt("page", UserConst.From.SINGLE)
                                        .withInt("lastPage", UserConst.LastFrom.MATCH)
                                        .withLong("id", it.id)
                                        .navigation()
                                }, {
                                    ToastGravity.showGravity(it.errorMsg)
                                })
                        } else {
                            //如果是女点击则判断有没有封面照 如果没有则进入封面照页面  如果有封面则开启直播坐等
                            if (context is LifecycleOwner) {
                                StartLiveProxy.builder(context, context)
                                    .startLive(context.mViewModel, LiveConst.Type.LIVE_AND_MATCH)
                            }
                        }
                    }
                }
            }

            "recharge" -> {
                val context = ViewUtils.getAliveTopActivity()
                if (context is BaseVmActivity<*>) {
                    GlobalPopupManager.showRechargePopup(
                        context,
                        context.mViewModel,
                        isNeedBottom = true
                    )
                }
            }

            "main" -> {
                val params = parseRouter(url.substringAfter("?"))
                if (params["force"] == "true") {
                    val context = ViewUtils.getAliveTopActivity()
                    if (context != null) {
                        val intent = Intent(context, MainActivity::class.java)

                        params.forEach {
                            intent.putExtra(it.key, it.value)
                        }

                        context.startActivity(intent)
                    }
                } else {
                    val tabIndex = params["tabIndex"]?.toIntOrNull()
                    val listIndex = params["listIndex"]?.toIntOrNull()

                    if (tabIndex != null) {
                        EventBus.getDefault().post(MainRouterEvent(tabIndex, listIndex))
                    }
                }
            }

            "tabbar" -> { // native://action=tabbar?type=<primaryPage>&page=<secondaryPage>
                val context = ViewUtils.getAliveTopActivity()
                val params = parseRouter(url.substringAfter("?"))
                if (context != null) {
                    val intent = Intent(context, MainActivity::class.java)
                    var mCurTabIndex = -1
                    params.forEach {
                        if (it.key == "type") {
                            mCurTabIndex = DisplayUtil.getCurrentIndexByPrimaryId(it.value.toInt())
                            intent.putExtra("tabIndex", mCurTabIndex.toString())
                        }
                        if (it.key == "page" && mCurTabIndex != -1) {
                            val realTabIndex =
                                DisplayUtil.getCurrentIndexBySecondaryPrimaryId(mCurTabIndex, it.value.toInt())
                            intent.putExtra("listIndex", realTabIndex.toString())
                        }
                    }
                    context.startActivity(intent)
                }
            }

            "startParty", "createParty" -> {
                EventBus.getDefault().post(StartPartyRouterEvent(true))
            }

            "firstLive" -> {
                //发送Event给MainActivity,然后沙雕顶部所有页面，之后在路由转跳
                if (!(LiveStateManager.isCalling()
                            || LiveStateManager.isLiving()
                            || PartyUserStateUtil.master
                            || PartyUserStateUtil.inTheMaiSeat
                            || PartyUserStateUtil.inTheGame
                            || PartyUserStateUtil.inTheGameSeat)
                ) {
                    val context = ViewUtils.getAliveTopActivity() ?: return
                    if (context is BaseVmActivity<*>) {
                        val intent = Intent(context, MainActivity::class.java)
                        intent.putExtra(
                            "tabIndex",
                            DisplayUtil.getCurrentIndexByPrimaryId(DisplayUtil.LIVE).toString()
                        )
                        intent.putExtra("listIndex", "2")

                        context.startActivity(intent)
                        context.mViewModel.request({
                            homeService.getChatParty(0)
                        }, {
                            val user = it.list.getOrNull(0) ?: return@request
                            //根据需求来这里直接写死路由为打开福袋
                            LiveUtils.invokeSpectator(context, user, "native://action=luckyBag")
                        })
                    }
                }
            }

            "luckyBag" -> {
                val context = ViewUtils.getAliveTopActivity() ?: return
                FragmentUtils.getFragmentManager(context)?.showNewDialogFragment(
                    LuckyBagMessageDialogFragment(),
                    LuckyBagMessageDialogFragment.FRAGMENT_TAG
                )
            }

            "rechargeAct" -> {
                val context = ViewUtils.getAliveTopActivity()
                if (context is BaseVmActivity<*>) {
                    GlobalDialogManager.showRechargeActivity(context, context.mViewModel)
                }
            }

            RouterControlManager.ROUTER_UP_MIC -> {
                RouterControlManager.dispatchMessage(RouterControlManager.ROUTER_UP_MIC, emptyMap())
            }

            RouterControlManager.ROUTER_GIFT -> {
                val params = parseRouter(url.substringAfter("?"))
                RouterControlManager.dispatchMessage(RouterControlManager.ROUTER_GIFT, params)
            }

            RouterControlManager.ROUTER_ROOMGAME -> { //打开幸运游戏列表
                val params = parseRouter(url.substringAfter("?"))
                RouterControlManager.dispatchMessage(RouterControlManager.ROUTER_ROOMGAME, params)
            }

            RouterControlManager.ROUTER_PARTYGAMEUP -> { //上游戏位
                RouterControlManager.dispatchMessage(RouterControlManager.ROUTER_PARTYGAMEUP, emptyMap())
            }
            //不支持的
            else -> showUnsupported(url)
        }

    }

    fun killTopActivity(routeUrl: String, pathUrl: String) {
        val list = ActivityUtils.getActivityList()
        val activeSpectatorRoutePath = getActiveSpectatorRoutePath(list)
        //如果转跳的路由在 activity栈中存在  则直接杀掉这个页面上所有的activity
        if (activeSpectatorRoutePath != null) {
            //直接弹掉顶部的
            XActivityUtils.killTopActivityTo(activeSpectatorRoutePath.second)
            // 如果在对应页面了  则判断主播id与路由id是否一致
            if (pathUrl == activeSpectatorRoutePath.first) {
                //拆参数  如果参数存在router则  继续转跳路由里的路由
                val routerUrl = routeUrl.substring(RouterUtils.Type.KEY_NATIVE.length)
                val params = RouterUtils.parseRouter(routerUrl.substringAfter("?"))
                val routerValue = params["router"]
                val anchorIdValue = params["anchorId"]
                //发送后在观众页判断当前的主播是不是一个人，如果是就不管了，如果不是则转跳
                EventBus.getDefault().post(
                    WebSpectatorEvent(
                        anchorId = anchorIdValue?.toLongOrNull(),
                        childRouter = EncodeUtils.urlDecode(routerValue)
                    )
                )
            } else {
                //如果不在对应的页面  比如 用户在派对页 但是 需要跳到游戏页
                routerGoto(routeUrl)
                EventBus.getDefault().post(WebSpectatorEvent(true))
            }
        } else {
            routerGoto(routeUrl)
        }
    }

    private fun getActiveSpectatorRoutePath(activities: List<Activity>): Pair<String, AppCompatActivity>? {
        return activities.find {
            it is LiveSpectatorActivity || it is PartySpectatorActivity || it is PartyGameSpectatorActivity
        }?.let { activity ->
            val route = when (activity) {
                is LiveSpectatorActivity -> RoutePath.LIVE_SPECTATOR_ACTIVITY
                is PartySpectatorActivity -> RoutePath.PARTY_SPECTATOR_ACTIVITY
                is PartyGameSpectatorActivity -> RoutePath.PARTY_GAME_SPECTATOR_ACTIVITY
                else -> return null // 这种情况基本是不会出现的
            }
            route to activity as AppCompatActivity
        }
    }
}

private fun showUnsupported(router: String) {
    if (ServerConfig.isDebug()) {
        ToastGravity.showGravity("Unsupported router $router")
    }
}